home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Speccy ClassiX 1998
/
Speccy ClassiX 98.iso
/
amiga_system
/
the_aminet
/
dev
/
gcc
/
ixemulsrc.lha
/
ixemul-41.4
/
stack
/
stkrst.c
< prev
next >
Wrap
C/C++ Source or Header
|
1995-05-23
|
2KB
|
61 lines
#include <bases.h>
asm("
| the stack consists of a single linked linear list like this:
|
| struct stack
| { struct stack *next; points to the next underlying structure
| struct StackSwapStruct sss; holds previous stackframe when used,
| itself when unused, the current stackborders
| are in the task structure ;-)
| APTR top_of_stackframe; } previous variable value
| Note: stack->sss.stk_Lower is not reliable
|
| For better performance stackframes are cached in a 'unused' list when
| not in use. (AllocMem() is really a performance killer).
|
|
| Caution:
| Race condition ahead! exec might preempt our task at any time storing
| the current register set on top of the free stack. NEVER set a sp higher
| than the location of important data.
|
.comm ___used_stack,8 | pointer to used stackframes,
| pointer to unused stackframes
.text
.even
.globl ___stkrst
___stkrst:
movel a2,sp@-
moveml #0x40f2,sp@-
movel sp,a2
movel d0,a3
l0: lea "A4(___used_stack)",a1
tstl a1@
beq l1 | No previous stackframe
movel "A4(___stackborders)",a0
cmpl a0@,a3
jcs l2
cmpl a0@(4:W),a3
jhi l2 | Stackpointer points to current frame
l1: movel a2@(28:W),a3@- | Store returnaddress
movel a3,d0
moveml a2@+,#0x4f02 | Restore registers
movel a2@,a2
movel d0,sp | Set stackpointer AFTER restoring registers!
addql #4,d0 | This function may return on the same
rts | stackframe it was called on.
l2: movel a1@,a0 | Go to previous stack
movel a0@,a1@+
movel a1@,a0@
movel a0,a1@
addqw #4,a0
movel a0@(12:W),"A4(___stk_limit)"
movel "A4(_SysBase)",a6
jsr a6@(-0x2dc) | StackSwap(sss:a0)
subqw #4,sp | Avoid overwriting returnaddress
jra l0
");